import asyncio

async def coroutine_add_one(number: int) -> int:
    return number + 1

#async将函数标记为协程
async def hello_world_message(str: str, sleep_seconds: int) -> None:
    await asyncio.sleep(sleep_seconds) # sleep本身就是一个协程
    print("hello " + str)

#运行协程
result = asyncio.run(coroutine_add_one(1)) 
print(result)

async def main() -> None:
    # 同一个async函数中 await间是串行 task间是并行
    job1 = await hello_world_message("zhoub", 4)
    job2 = await hello_world_message("zhouyc", 2)

    print(job1)
    print("job1 finished")
    print(job2)

    #2.3 通过任务实现并行
    sleep_4 = asyncio.create_task(hello_world_message("zhoub task", 10))
    print("after create task zhoub 4")
    sleep_2 = asyncio.create_task(hello_world_message("zhouyc task", 2))

    sleep_4.cancel()

    try:
        await sleep_4  #可以取消task 取消时抛出的错误只能由await语句引发。调用取消任务时不会立刻停止任务，只有当前处于等待点或其下一个等待点时才会停止任务
    except asyncio.CancelledError:
        print("CancelledError from sleep_4!")

    print("这里应该大概距离create_task zhoub的任务10秒左右")
    await sleep_2
    print("因为zhoubyc的任务是2秒 所以早已经执行完了 这块基本也是10秒左右到达")
    print("这里可以多个任务执行然后通过await获取多个任务结果进行合并处理")

    #2.4.2 带超时的任务
    sleep_timeout = asyncio.create_task(hello_world_message("timeout task", 10))
    try:
        await asyncio.wait_for(sleep_timeout, timeout=2)
    except asyncio.exceptions.TimeoutError:
        print("TimeoutError from sleep_timeout")
    
    #2.4.2 shield可以保护传入的协程被取消 给它一个屏蔽 取消请求将被忽略
    shield_timeout = asyncio.create_task(hello_world_message("shield_timeout task", 10))
    try:
        await asyncio.wait_for(asyncio.shield(shield_timeout), timeout=2)
    except asyncio.exceptions.TimeoutError:
        print("TimeoutError from shield_timeout")
        await shield_timeout #利用await等待最初的任务完成
        print("shield_timeout completed")

asyncio.run(main()) # 运行协程 它只执行一个协程 使用这个函数作为入口点去执行其它协程


